package com.durian.ui.adapter.multi;

import android.view.ViewGroup;
import androidx.annotation.NonNull;
import androidx.lifecycle.LifecycleOwner;
import androidx.recyclerview.widget.RecyclerView;
import java.util.Collection;
import java.util.List;

/**
 * 说明：MultiTypeAdapter
 * <p/>
 * 作者：fanly
 * <p/>
 * 类型：Class
 * <p/>
 * 时间：2016/11/28 15:08
 * <p/>
 * 版本：version 1.0
 */
public class MultiTypeAdapter<T> extends RecyclerView.Adapter<RecyclerView.ViewHolder>{

    protected final List<T> items;
    protected TypePool delegate;

    public MultiTypeAdapter(){
        this(new Items());
    }

    public MultiTypeAdapter(@NonNull List<T> items) {
        this.delegate = new MultiTypePool();
        this.items = items;
    }

    public void setLifecycleOwner(LifecycleOwner lifecycleOwner){
        if (lifecycleOwner != null){
            lifecycleOwner.getLifecycle().addObserver(new MultiTypeLifecycle(this));
        }
    }

    public MultiTypeAdapter register(@NonNull Class<?> clazz, @NonNull ViewProvider provider) {
        delegate.register(clazz, provider);
        return this;
    }

    @Override
    public int getItemViewType(int position) {
        T item = items.get(position);
        return delegate.getViewTypeByClass(item.getClass(),item);
    }

    @Override
    public RecyclerView.ViewHolder onCreateViewHolder(ViewGroup parent, int viewType) {
        return delegate.createViewHolder(this, parent, viewType);
    }

    @Override
    public void onBindViewHolder(RecyclerView.ViewHolder holder, int position) {
        delegate.bindViewHolder(this,holder,position);
    }

    public <T> ViewProvider getViewProviderByItem(@NonNull Class<?> clazz,@NonNull T item){
        return delegate.getViewProviderByItem(clazz,item);
    }

    public T get(int position){
        return items.get(position);
    }

    @Override
    public int getItemCount() {
        return items.size();
    }


    public List<T> getData() {
        return items;
    }

    public boolean isEmpty() {
        return items == null || items.isEmpty();
    }

    /**
     * 添加一条数据到底部
     *
     * @param item
     */
    public void add(T item) {
        if (item != null) {
            items.add(item);
            notifyItemRangeChanged(items.size() - 1, 1);
        }
    }

    /**
     * 说明：添加数据
     *
     * @param position
     * @param item
     */
    public void add(int position, T item) {
        if (item != null && position >= 0 && position < items.size()) {
            items.add(position, item);
            notifyItemInserted(position);
        }
    }

    /**
     * 说明：添加数据
     *
     * @param position
     * @param data
     */
    public void addAll(int position, List<T> data) {
        if (data == null) {
            return;
        }
        if (position >= 0 && position <= items.size()) {
            items.addAll(position, data);
            notifyItemRangeChanged(position, data.size());
        }
    }

    /**
     * 说明：添加数据
     *
     * @param data
     */
    public void addAll(List<T> data) {
        if (data == null) {
            return;
        }
        items.addAll(data);
        notifyItemRangeChanged(items.size() - data.size() - 1, data.size());
    }


    /**
     * 说明：删除数据
     *
     * @param position
     */
    public void removeAtIndex(int position) {
        if (checkPostion(position)) {
            items.remove(position);
            notifyDataSetChanged();
        }
    }

    public void removeAll(Collection<?> list) {
        if (list != null && !list.isEmpty()) {
            items.removeAll(list);
            notifyDataSetChanged();
        }
    }

    /**
     * 批量删除
     *
     * @param startPosition
     */
    public void removeBatch(int startPosition) {
        for (int i = items.size() - 1; i >= startPosition; i--) {
            items.remove(i);
            notifyItemRemoved(i);//通知移除该条
            notifyItemRangeChanged(i, items.size() - i);//更新适配器这条后面列表的变化
        }
    }

    /**
     * 说明：删除数据
     *
     * @param t
     */
    public void remove(T t) {
        if (items != null && items.contains(t)) {
            items.remove(t);
            notifyDataSetChanged();
        }
    }

    /**
     * 说明：修改数据
     *
     * @param position
     * @param item
     */
    public void changed(int position, T item) {
        if (checkPostion(position) && item != null) {
            items.set(position, item);
            notifyItemChanged(position);
        }
    }

    /**
     * 说明：刷新数据
     *
     * @param data
     */
    public void refresh(List<T> data) {
        items.clear();
        if (data != null) {
            items.addAll(data);
        }
        notifyDataSetChanged();
    }

    public void offsetPosition(int offset){
        delegate.offsetPosition(offset);
    }

    private boolean checkPostion(int position) {
        return position >= 0 && position < items.size();
    }

    public void onDestroy() {
        delegate.onDestroy();
    }
}
